﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using Microsoft.Web.WebView2.Core;
using Microsoft.Win32;

namespace WebPageDownloader2
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();

            webView.CoreWebView2InitializationCompleted += WebView_CoreWebView2InitializationCompleted;
            urlTextBox.KeyUp += OnUrlTextBoxKeyUp;
        }

        private void WebView_CoreWebView2InitializationCompleted(object sender, CoreWebView2InitializationCompletedEventArgs e)
        {
            webView.CoreWebView2.NewWindowRequested += CoreWebView2_NewWindowRequested;
        }


        private async void OnSaveButtonClickAsync(object sender, RoutedEventArgs e)
        {
            if (webView.IsLoaded)
            {
                var content = await webView.ExecuteScriptAsync("document.documentElement.outerHTML;");
                content = Regex.Unescape(content);
                content = content.Remove(0, 1);
                content = content.Remove(content.Length - 1, 1);
                if (DisableJavaScriptCheckBox.IsChecked == true)
                {
                    content = ReplaceString(content, "<javascript", "<!--<javascript");
                    content = ReplaceString(content, "</javascript>", "</javascript>-->");
                    content = ReplaceString(content, "<script", "<!--<script");
                    content = ReplaceString(content, "</script>", "</script>-->");
                }
                OpenFileDialog fileDialog = new OpenFileDialog();
                fileDialog.Filter = "网页文件|*.html;*.htm";
                fileDialog.Multiselect = false;
                fileDialog.CheckFileExists = false;
                fileDialog.CheckPathExists = true;
                var result = fileDialog.ShowDialog(this);
                if (true == result)
                {
                    using (var fileStream = File.Create(fileDialog.FileName))
                    {
                        using (var writer = new StreamWriter(fileStream))
                        {
                            writer.Write(content);
                            writer.Flush();
                        }
                    }
                    if (MessageBox.Show($"文件已保存到路径\n{fileDialog.FileName}\n需要加载吗？", "提示", MessageBoxButton.YesNo) == MessageBoxResult.Yes)
                    {
                        urlTextBox.Text = fileDialog.FileName;
                        webView.CoreWebView2.Navigate(urlTextBox.Text);
                    }
                }
            }
            else
            {
                MessageBox.Show("请等待页面加载后再保存。", "错误");
            }
        }

        private void OnBackButtonClick(object sender, RoutedEventArgs e)
        {
            if (webView.CanGoBack)
            {
                webView.GoBack();
            }
        }

        private void OnForwardButtonClick(object sender, RoutedEventArgs e)
        {
            if (webView.CanGoForward)
            {
                webView.GoForward();
            }
        }

        private void OnUrlTextBoxKeyUp(object sender, KeyEventArgs e)
        {
            if (e.Key != Key.Enter)
            {
                return;
            }
            var url = urlTextBox.Text.Trim();
            if (!Uri.TryCreate(url, UriKind.RelativeOrAbsolute, out Uri uri))
            {
                MessageBox.Show("请输入正确网址。", "错误");
                return;
            }
            if (!url.Contains(":"))
            {
                url = "http://" + url;
            }

            if (webView != null)
            {
                if (webView.CoreWebView2 != null)
                {
                    webView.CoreWebView2.Navigate(url);

                }
                else
                {
                    var result =
                            MessageBox.Show("无法加载网页，需要从以下网址安装MicrosoftEdgeWebview2运行环境：\r\nhttps://go.microsoft.com/fwlink/p/?LinkId=2124703\r\n是否需要下载？", "提示", MessageBoxButton.YesNo, MessageBoxImage.Warning);
                    if (result == MessageBoxResult.Yes)
                    {
                        //从注册表中读取默认浏览器可执行文件路径
                        RegistryKey key = Registry.ClassesRoot.OpenSubKey(@"http\shell\open\command\");
                        string cmd = key.GetValue("").ToString();
                        if (cmd.Contains("\""))
                        {
                            cmd = cmd.Substring(cmd.IndexOf("\"") + 1, cmd.LastIndexOf("\"") - cmd.IndexOf("\"") - 1);
                        }

                        System.Diagnostics.Process.Start(cmd, "https://go.microsoft.com/fwlink/p/?LinkId=2124703");

                        MessageBox.Show("请下载后安装文件，并重启程序", "提示");
                    }
                }
            }
        }

        private void OnRefreshButtonClick(object sender, RoutedEventArgs e)
        {
            if (!string.IsNullOrWhiteSpace(urlTextBox.Text))
            {
                webView.Reload();
            }
        }

        private void OnNavigating(object sender, CoreWebView2NavigationStartingEventArgs e)
        {
            progressTextBlock.Visibility = Visibility.Visible;
            if (urlTextBox.Text != e.Uri.ToString())
            {
                urlTextBox.Text = e.Uri.ToString();
            }
        }

        private void OnNavigated(object sender, CoreWebView2NavigationCompletedEventArgs e)
        {
            progressTextBlock.Visibility = Visibility.Collapsed;
        }

        private string ReplaceString(string rawContent, string regEx, string replacement)
        {
            var regex = new Regex(regEx, RegexOptions.Compiled | RegexOptions.IgnoreCase);
            return regex.Replace(rawContent, replacement);
        }

        private void CoreWebView2_NewWindowRequested(object sender, CoreWebView2NewWindowRequestedEventArgs e)
        {
            if (HookNewWindowCheckBox.IsChecked == true)
            {   
                e.Handled = true;
                webView.CoreWebView2.Navigate(e.Uri);
            }
        }
    }
}
